--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
Node / ReticulumProjects / MeshChatX.git / files / scripts / ci / github-upload-bunny-storage-release-assets.py
Displaying Raw • Download
scripts/ci/github-upload-bunny-storage-release-assets.py 229c67e377499d3a81535597882388380f1a9b3f (229c67e3) Text, 3.18 KB
T8b949e#!/usr/bin/env python3
T8b949e"""Upload a directory tree to bunny.net Edge Storage (HTTP PUT per object)."""
Tff7b72from T7ee787__future__ Tff7b72import Te6edf3annotations
Tff7b72import T7ee787hashlib
Tff7b72import T7ee787mimetypes
Tff7b72import T7ee787os
Tff7b72import T7ee787sys
Tff7b72import T7ee787time
Tff7b72import T7ee787urllibT7ee787.T7ee787error
Tff7b72import T7ee787urllibT7ee787.T7ee787request
Tff7b72from T7ee787pathlib Tff7b72import Te6edf3Path
Tff7b72from T7ee787urllibT7ee787.T7ee787parse Tff7b72import Te6edf3quote
Tff7b72def Td2a8ffencode_object_relTb4b4b4(Te6edf3relTb4b4b4: Tffa657strTb4b4b4) Tff7b72-Tff7b72> Tffa657strTb4b4b4:
Tff7b72return Ta5d6ff"Ta5d6ff/Ta5d6ff"Tff7b72.Td2a8ffjoinTb4b4b4(Te6edf3quoteTb4b4b4(Te6edf3partTb4b4b4, Te6edf3safeTff7b72=Ta5d6ff"Ta5d6ff"Tb4b4b4) Tff7b72for Te6edf3part Tff7b72in Te6edf3relTff7b72.Td2a8ffsplitTb4b4b4(Ta5d6ff"Ta5d6ff/Ta5d6ff"Tb4b4b4)Tb4b4b4)
Tff7b72def Td2a8ffmime_forTb4b4b4(Te6edf3pathTb4b4b4: Te6edf3PathTb4b4b4) Tff7b72-Tff7b72> Tffa657strTb4b4b4:
Tff7b72if Te6edf3pathTff7b72.Td2a8ffsuffixTff7b72.Td2a8fflowerTb4b4b4(Tb4b4b4) Tff7b72== Ta5d6ff"Ta5d6ff.wasmTa5d6ff"Tb4b4b4:
Tff7b72return Ta5d6ff"Ta5d6ffapplication/wasmTa5d6ff"
Te6edf3guessedTb4b4b4, Te6edf3_enc Tff7b72= Te6edf3mimetypesTff7b72.Td2a8ffguess_typeTb4b4b4(Te6edf3pathTff7b72.Td2a8ffnameTb4b4b4)
Tff7b72return Te6edf3guessed Tff7b72or Ta5d6ff"Ta5d6ffapplication/octet-streamTa5d6ff"
Tff7b72def Td2a8ffput_fileTb4b4b4(
Te6edf3urlTb4b4b4: Tffa657strTb4b4b4,
Te6edf3bodyTb4b4b4: Tffa657bytesTb4b4b4,
Te6edf3access_keyTb4b4b4: Tffa657strTb4b4b4,
Te6edf3content_typeTb4b4b4: Tffa657strTb4b4b4,
Te6edf3max_attemptsTb4b4b4: Tffa657int Tff7b72= T79c0ff4Tb4b4b4,
Tb4b4b4) Tff7b72-Tff7b72> Tff7b72NoneTb4b4b4:
Te6edf3checksum Tff7b72= Te6edf3hashlibTff7b72.Td2a8ffsha256Tb4b4b4(Te6edf3bodyTb4b4b4)Tff7b72.Td2a8ffhexdigestTb4b4b4(Tb4b4b4)Tff7b72.Td2a8ffupperTb4b4b4(Tb4b4b4)
Te6edf3timeout Tff7b72= T79c0ff600 Tff7b72if Tffa657lenTb4b4b4(Te6edf3bodyTb4b4b4) Tff7b72> T79c0ff50_000_000 Tff7b72else T79c0ff120
Tff7b72for Te6edf3attempt Tff7b72in Tffa657rangeTb4b4b4(T79c0ff1Tb4b4b4, Te6edf3max_attempts Tff7b72+ T79c0ff1Tb4b4b4)Tb4b4b4:
Te6edf3req Tff7b72= Te6edf3urllibTff7b72.Td2a8ffrequestTff7b72.Td2a8ffRequestTb4b4b4(
Te6edf3urlTb4b4b4,
Te6edf3dataTff7b72=Te6edf3bodyTb4b4b4,
Te6edf3methodTff7b72=Ta5d6ff"Ta5d6ffPUTTa5d6ff"Tb4b4b4,
Te6edf3headersTff7b72=Tb4b4b4{
Ta5d6ff"Ta5d6ffAccessKeyTa5d6ff"Tb4b4b4: Te6edf3access_keyTb4b4b4,
Ta5d6ff"Ta5d6ffContent-TypeTa5d6ff"Tb4b4b4: Te6edf3content_typeTb4b4b4,
Ta5d6ff"Ta5d6ffChecksumTa5d6ff"Tb4b4b4: Te6edf3checksumTb4b4b4,
Tb4b4b4}Tb4b4b4,
Tb4b4b4)
Tff7b72tryTb4b4b4:
Tff7b72with Te6edf3urllibTff7b72.Td2a8ffrequestTff7b72.Td2a8ffurlopenTb4b4b4(Te6edf3reqTb4b4b4, Te6edf3timeoutTff7b72=Te6edf3timeoutTb4b4b4) Tff7b72as Te6edf3respTb4b4b4:
Te6edf3code Tff7b72= Te6edf3respTff7b72.Td2a8ffgetcodeTb4b4b4(Tb4b4b4)
Tff7b72except Te6edf3urllibTff7b72.Td2a8fferrorTff7b72.Td2a8ffHTTPError Tff7b72as Te6edf3eTb4b4b4:
Te6edf3code Tff7b72= Te6edf3eTff7b72.Td2a8ffcode
Te6edf3err_body Tff7b72= Te6edf3eTff7b72.Td2a8ffreadTb4b4b4(T79c0ff500Tb4b4b4)
Tff7b72if Te6edf3code Tff7b72in Tb4b4b4(T79c0ff200Tb4b4b4, T79c0ff201Tb4b4b4)Tb4b4b4:
Tff7b72return
Tff7b72if T79c0ff500 Tff7b72<Tff7b72= Te6edf3code Tff7b72< T79c0ff600 Tff7b72and Te6edf3attempt Tff7b72< Te6edf3max_attemptsTb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.5 Tff7b72* Tb4b4b4(T79c0ff2 Tff7b72*Tff7b72* Tb4b4b4(Te6edf3attempt Tff7b72- T79c0ff1Tb4b4b4)Tb4b4b4)Tb4b4b4)
Tff7b72continue
Tff7b72raise Tf85149SystemExitTb4b4b4(
Ta5d6fffTa5d6ff"Ta5d6ffHTTP Tffd700{Te6edf3codeTffd700}Ta5d6ff for Tffd700{Te6edf3urlTffd700}Ta5d6ff: Tffd700{Te6edf3err_bodyTffd700!r}Ta5d6ff"Tb4b4b4,
Tb4b4b4) Tff7b72from T7ee787e
Tff7b72except Tb4b4b4(Te6edf3urllibTff7b72.Td2a8fferrorTff7b72.Td2a8ffURLErrorTb4b4b4, Tf85149TimeoutErrorTb4b4b4) Tff7b72as Te6edf3eTb4b4b4:
Tff7b72if Te6edf3attempt Tff7b72< Te6edf3max_attemptsTb4b4b4:
Te6edf3timeTff7b72.Td2a8ffsleepTb4b4b4(T79c0ff0.5 Tff7b72* Tb4b4b4(T79c0ff2 Tff7b72*Tff7b72* Tb4b4b4(Te6edf3attempt Tff7b72- T79c0ff1Tb4b4b4)Tb4b4b4)Tb4b4b4)
Tff7b72continue
Tff7b72raise Tf85149SystemExitTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffrequest failed for Tffd700{Te6edf3urlTffd700}Ta5d6ff: Tffd700{Te6edf3eTffd700}Ta5d6ff"Tb4b4b4) Tff7b72from T7ee787e
Tff7b72elseTb4b4b4:
Tff7b72if Te6edf3code Tff7b72in Tb4b4b4(T79c0ff200Tb4b4b4, T79c0ff201Tb4b4b4)Tb4b4b4:
Tff7b72return
Tff7b72raise Tf85149SystemExitTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffunexpected status Tffd700{Te6edf3codeTffd700}Ta5d6ff for Tffd700{Te6edf3urlTffd700}Ta5d6ff"Tb4b4b4)
Tff7b72def Td2a8ffmainTb4b4b4(Tb4b4b4) Tff7b72-Tff7b72> Tff7b72NoneTb4b4b4:
Te6edf3base Tff7b72= Te6edf3osTff7b72.Td2a8ffenvironTff7b72.Td2a8ffgetTb4b4b4(Ta5d6ff"Ta5d6ffBUNNY_STORAGE_BASE_URLTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ff"Tb4b4b4)Tff7b72.Td2a8ffrstripTb4b4b4(Ta5d6ff"Ta5d6ff/Ta5d6ff"Tb4b4b4)
Te6edf3key Tff7b72= Te6edf3osTff7b72.Td2a8ffenvironTff7b72.Td2a8ffgetTb4b4b4(Ta5d6ff"Ta5d6ffBUNNY_STORAGE_ACCESS_KEYTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ff"Tb4b4b4)
Te6edf3prefix Tff7b72= Te6edf3osTff7b72.Td2a8ffenvironTff7b72.Td2a8ffgetTb4b4b4(Ta5d6ff"Ta5d6ffBUNNY_STORAGE_OBJECT_PREFIXTa5d6ff"Tb4b4b4, Ta5d6ff"Ta5d6ff"Tb4b4b4)Tff7b72.Td2a8ffstripTb4b4b4(Ta5d6ff"Ta5d6ff/Ta5d6ff"Tb4b4b4)
Tff7b72if Tff7b72not Te6edf3base Tff7b72or Tff7b72not Te6edf3keyTb4b4b4:
Tffa657printTb4b4b4(
Ta5d6ff"Ta5d6ffBUNNY_STORAGE_BASE_URL and BUNNY_STORAGE_ACCESS_KEY must be setTa5d6ff"Tb4b4b4,
Te6edf3fileTff7b72=Te6edf3sysTff7b72.Td2a8ffstderrTb4b4b4,
Tb4b4b4)
Te6edf3sysTff7b72.Td2a8ffexitTb4b4b4(T79c0ff1Tb4b4b4)
Te6edf3root Tff7b72= Te6edf3PathTb4b4b4(Te6edf3sysTff7b72.Td2a8ffargvTb4b4b4[T79c0ff1Tb4b4b4]Tb4b4b4)Tff7b72.Td2a8ffresolveTb4b4b4(Tb4b4b4)
Tff7b72if Tff7b72not Te6edf3rootTff7b72.Td2a8ffis_dirTb4b4b4(Tb4b4b4)Tb4b4b4:
Tffa657printTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffnot a directory: Tffd700{Te6edf3rootTffd700}Ta5d6ff"Tb4b4b4, Te6edf3fileTff7b72=Te6edf3sysTff7b72.Td2a8ffstderrTb4b4b4)
Te6edf3sysTff7b72.Td2a8ffexitTb4b4b4(T79c0ff1Tb4b4b4)
Te6edf3files Tff7b72= Tffa657sortedTb4b4b4(Te6edf3p Tff7b72for Te6edf3p Tff7b72in Te6edf3rootTff7b72.Td2a8ffrglobTb4b4b4(Ta5d6ff"Ta5d6ff*Ta5d6ff"Tb4b4b4) Tff7b72if Te6edf3pTff7b72.Td2a8ffis_fileTb4b4b4(Tb4b4b4)Tb4b4b4)
Tff7b72if Tff7b72not Te6edf3filesTb4b4b4:
Tffa657printTb4b4b4(Ta5d6fffTa5d6ff"Ta5d6ffno files under Tffd700{Te6edf3rootTffd700}Ta5d6ff"Tb4b4b4, Te6edf3fileTff7b72=Te6edf3sysTff7b72.Td2a8ffstderrTb4b4b4)
Te6edf3sysTff7b72.Td2a8ffexitTb4b4b4(T79c0ff1Tb4b4b4)
Tff7b72for Te6edf3path Tff7b72in Te6edf3filesTb4b4b4:
Te6edf3rel Tff7b72= Te6edf3pathTff7b72.Td2a8ffrelative_toTb4b4b4(Te6edf3rootTb4b4b4)Tff7b72.Td2a8ffas_posixTb4b4b4(Tb4b4b4)
Tff7b72if Te6edf3prefixTb4b4b4:
Te6edf3object_rel Tff7b72= Ta5d6fffTa5d6ff"Tffd700{Te6edf3prefixTffd700}Ta5d6ff/Tffd700{Te6edf3relTffd700}Ta5d6ff"
Tff7b72elseTb4b4b4:
Te6edf3object_rel Tff7b72= Te6edf3rel
Te6edf3url Tff7b72= Ta5d6fffTa5d6ff"Tffd700{Te6edf3baseTffd700}Ta5d6ff/Tffd700{Te6edf3encode_object_relTb4b4b4(Te6edf3object_relTb4b4b4)Tffd700}Ta5d6ff"
Te6edf3body Tff7b72= Te6edf3pathTff7b72.Td2a8ffread_bytesTb4b4b4(Tb4b4b4)
Te6edf3put_fileTb4b4b4(Te6edf3urlTb4b4b4, Te6edf3bodyTb4b4b4, Te6edf3keyTb4b4b4, Te6edf3mime_forTb4b4b4(Te6edf3pathTb4b4b4)Tb4b4b4)
Tffa657printTb4b4b4(Te6edf3urlTb4b4b4)
Tff7b72if Tff7b72__name__ Tff7b72== Ta5d6ff"Ta5d6ff__main__Ta5d6ff"Tb4b4b4:
Te6edf3mainTb4b4b4(Tb4b4b4)
──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────